package com.topsun.framework.common.core.util;

import cn.hutool.core.util.ObjectUtil;

import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * 
 * @author: 皮皮
 * @date: 2022/1/7 5:41 下午
 */
public class CollUtil extends cn.hutool.core.collection.CollUtil {

    /**
     * 获取集合中的属性，返回Set集合
     *
     * @param collection 集合
     * @param mapper 属性映射器
     * @param <T> 集合元素泛型
     * @param <E> 返回Set元素泛型
     * @return Set  返回集合元素的属性Set集合，进行去重
     */
    public static <T, E> Set<E> filedSet(Collection<T> collection, Function<? super T, ? extends E> mapper) {
        return Optional.ofNullable(collection).orElse(newArrayList()).stream()
                .map(mapper)
                .collect(Collectors.toSet());
    }

    /**
     * 获取集合中的属性，返回Set集合
     * 注：NULL会被过滤掉
     *
     * @param collection 集合
     * @param mapper 属性映射器
     * @param <T> 集合元素泛型
     * @param <E> 返回Set元素泛型
     * @return Set  返回集合元素的属性Set集合，进行去重
     */
    public static <T, E> Set<E> filedSetNotNull(Collection<T> collection, Function<? super T, ? extends E> mapper) {
        return Optional.ofNullable(collection).orElse(newArrayList()).stream()
                .filter(ObjectUtil::isNotNull)
                .map(mapper)
                .filter(ObjectUtil::isNotNull)
                .collect(Collectors.toSet());
    }

    /**
     * 获取集合中的属性，返回Set集合
     * 注：NULL会被过滤掉
     *
     * @param collection 集合
     * @param mapper 属性映射器
     * @param <T>  集合元素泛型
     * @param <E> 返回List元素泛型
     * @return List<E> 返回属性集合列表
     */
    public static <T, E> List<E> filedList(Collection<T> collection, Function<? super T, ? extends E> mapper) {
        return Optional.ofNullable(collection).orElse(newArrayList()).stream()
                .map(mapper)
                .collect(Collectors.toList());
    }

    /**
     * 获取集合中的属性，返回Set集合
     * 注：NULL会被过滤掉
     *
     * @param collection 集合
     * @param mapper 属性映射器
     * @param <T>  集合元素泛型
     * @param <E> 返回List元素泛型
     * @return List<E> 返回属性集合列表
     */
    public static <T, E> List<E> filedListNotNull(Collection<T> collection, Function<? super T, ? extends E> mapper) {
        return Optional.ofNullable(collection).orElse(newArrayList()).stream()
                .filter(ObjectUtil::isNotNull)
                .map(mapper)
                .filter(ObjectUtil::isNotNull)
                .collect(Collectors.toList());
    }

    /**
     * 集合转换map
     *
     * @param collection 要转换的集合
     * @param KeyMapper key表达式
     * @param valueMapper value表达式
     * @param <T> 集合元素泛型
     * @param <K> key泛型
     * @param <V> value泛型
     * @return
     */
    public static <T, K, V> Map<K, V> coll2Map(Collection<T> collection, Function<T, K> KeyMapper, Function<T, V> valueMapper) {
        return Optional.ofNullable(collection).orElse(CollUtil.newArrayList()).stream()
                .collect(Collectors.toMap(KeyMapper, valueMapper));
    }

    /**
     * 集合转换map
     * 注：key value为NULL的，会被过滤掉，因为Collectors.toMap会NPE
     *
     * @param collection 要转换的集合
     * @param KeyMapper key表达式
     * @param valueMapper value表达式
     * @param <T> 集合元素泛型
     * @param <K> key泛型
     * @param <V> value泛型
     * @return
     */
    public static <T, K, V> Map<K, V> coll2MapNotNull(Collection<T> collection, Function<T, K> KeyMapper, Function<T, V> valueMapper) {
        return Optional.ofNullable(collection).orElse(CollUtil.newArrayList()).stream()
                .filter(data -> Objects.nonNull(data) && Objects.nonNull(KeyMapper.apply(data)) && Objects.nonNull(valueMapper.apply(data)))
                .collect(Collectors.toMap(KeyMapper, valueMapper));
    }


}
